package hawk.example.jdk.stream;

import static hawk.example.jdk.stream.Shower.show;

import java.util.Arrays;
import java.util.List;
import java.util.stream.Stream;

public class TransformStreams {

    public static void main(String[] args) {
        filter();
        map();
        flatmap();
        mapMulti();
    }

    public static void filter() {
        List<String> words = Arrays.asList("hello", "world", "beautiful", "LongLongAgo", "12345678910abcdef");
        Stream<String> longWords = words.stream().filter(w -> w.length() > 10);
        show("filter", longWords);
    }

    public static void map() {
        List<String> words = Arrays.asList("h ello  ", "wo rld  ");
        Stream<String> uppercaseWords = words.stream().map(String::toUpperCase);
        show("Stream<String> to Stream<String> map", uppercaseWords);

        Stream<Stream<String>> result = words.stream().map(w -> (codePoints(w)));
        show("Stream<String> to Stream<Stream<String>> map", result);
    }

    public static void flatmap() {
        List<String> words = Arrays.asList("h ello  ", "wo rld  ");
        Stream<String> result = words.stream().flatMap(TransformStreams::codePoints);
        show("flatmap", result);
    }

    public static void mapMulti() {
        List<String> words = Arrays.asList("h ello  ", "wo rld  ");
        String sentence = "abcdiefalshfosfhsafhwiehfasfccasfsdfsfsdl";
        Stream<String> result = words.stream().mapMulti(((s,collector) -> {
            int i = 0;
            while (i < s.length()) {
                int cp = sentence.codePointAt(i);
                // collector.accept(cp+"1");
                collector.accept(cp+"1");
                // System.out.println(collector.getClass().getName());
                if (Character.isSupplementaryCodePoint(cp))
                    i += 2;
                else
                    i++;
            }
        }));
        show("mapMulti", result);
    }

    public static Stream<String> codePoints(String s) {
        return s.codePoints().mapToObj(cp -> new String(new int[] { cp }, 0, 1));
    }
}
